package com.example.demo.service;

import com.alibaba.fastjson.JSONObject;
import com.example.demo.common.Func;
import lombok.extern.slf4j.Slf4j;
import org.springframework.mail.javamail.JavaMailSenderImpl;
import org.springframework.mail.javamail.MimeMessageHelper;
import org.springframework.scheduling.annotation.Async;
import org.springframework.scheduling.annotation.AsyncResult;
import org.springframework.stereotype.Service;

import java.nio.file.Files;
import java.nio.file.Paths;
import java.util.Date;
import java.util.Properties;
import java.util.concurrent.CompletableFuture;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.Future;

@Service
@Slf4j
public class AsyncService {

    @Async("sendEmailAsync")
    public void writeLog(JSONObject jsLog, String type) {
        //将日志用多线程写入数据库
    }

    @Async("sendEmailAsync")
    public Future<String> getEmail() {
        try {
            log.info("异步开始执行");
            Thread.sleep(1000);
            log.info("异步结束执行");
        } catch (InterruptedException e) {
            e.printStackTrace();
            return new AsyncResult<>("异步执行出错了");
        }
        return new AsyncResult<>("异步任务执行完成");
    }

    @Async("sendEmailAsync")
    public Future<String> getInfo1(CountDownLatch latch) {
        try {
            log.info("getInfo1:开始执行");
            Thread.sleep(1000);
            log.info("getInfo1:结束");
        } catch (InterruptedException e) {
            e.printStackTrace();
            return new AsyncResult<>("getInfo1:出错了");
        } finally {
            latch.countDown();
        }
        return new AsyncResult<>("getInfo1:完成");
    }

    @Async("sendEmailAsync")
    public Future<String> getInfo2(CountDownLatch latch) {
        try {
            log.info("getInfo2:开始执行");
            Thread.sleep(3000);
            log.info("getInfo2:结束");
        } catch (InterruptedException e) {
            e.printStackTrace();
            return new AsyncResult<>("getInfo2:出错了");
        } finally {
            latch.countDown();
        }
        return new AsyncResult<>("getInfo2:完成");
    }

    @Async("sendEmailAsync")
    public CompletableFuture<String> getInfo3() {
        try {
            // 模拟可能抛出异常的代码
            Thread.sleep(2000);
            log.info("getInfo3:线程结束");
            return CompletableFuture.completedFuture("线程执行成功");
        } catch (Exception e) {
            log.info("getInfo3:线程失败");
            return CompletableFuture.completedFuture("线程执行失败，异常：" + e.getMessage());
        }
    }

    @Async("sendEmailAsync")
    public void email() {
        try {
            // 不写在配置文件里，是为了将邮箱信息放在管理后台
            JavaMailSenderImpl mailSender = new JavaMailSenderImpl();
            mailSender.setHost("smtp.qq.com");
            mailSender.setUsername("214510115@qq.com");
            mailSender.setPassword("dqqyvmzxepjucace");
            mailSender.setPort(465);
            mailSender.setDefaultEncoding("utf-8");
            mailSender.setProtocol("smtps");

            Properties properties = new Properties();
            properties.put("mail.smtp.connectiontimeout", 5000);
            properties.put("mail.smtp.timeout", 3000);
            properties.put("mail.smtp.writetimeout", "5000");
            properties.put("mail.smtp.auth", true);
            properties.put("mail.smtp.starttls.enable", true);
            properties.put("mail.smtp.starttls.required", true);
            mailSender.setJavaMailProperties(properties);

            MimeMessageHelper helper = new MimeMessageHelper(mailSender.createMimeMessage(), true);
            helper.setFrom("214510115@qq.com", "招信宝官网");
            helper.setTo("543982146@qq.com");
            helper.setSubject("测试JAVA发送QQ邮件");
            helper.setText("娶个好老婆：<strong>王彦远与陈艺文</strong>", true);
            helper.setSentDate(new Date());
            helper.addAttachment("招信宝合同文档.ftl",
                    () -> Files.newInputStream(Paths.get(Func.getRootPath() + "/file/template/apply1.ftl")),
                    "application/octet-stream");
            helper.addAttachment("招信宝使用说明.ftl",
                    () -> Files.newInputStream(Paths.get(Func.getRootPath() + "/file/template/apply1.ftl")),
                    "application/octet-stream");

            // 另一种发送附件的方法
            /*FileSystemResource file = new FileSystemResource(new File("f:/SpringBoot项目实战案例锦集.pdf"));
            helper.addAttachment("SpringBoot项目实战案例锦集.pdf", file);*/

            // 发送内嵌资源（先添加文本，再添加资源）
            /*helper.setText("感谢 <b>罗海林</b>, 关注《Spring全家桶实战案例源码》<br/><img src='cid:id_un_123'/>", true);
            helper.addInline("id_un_123", file);*/

            mailSender.send(helper.getMimeMessage());

            log.info("发送邮件成功");
            log.info(Thread.currentThread().getName());
        }
        catch (Exception ex) {
            log.error("发送异常：" + ex);
        }
    }

}
